<template>
  <div class="avatar-container">
    <a-modal
        title="头像上传"
        v-model:open="showCropper"
        width="800px"
        :footer="null"
        destroyOnClose
        @cancel="beforeClose"
    >
      <a-row>
        <a-col :span="12" style="height: 300px">
          <VueCropper
              ref="cropper"
              :img="options.img"
              :info="true"
              :autoCrop="options.autoCrop"
              :autoCropWidth="options.autoCropWidth"
              :autoCropHeight="options.autoCropHeight"
              :fixedBox="options.fixedBox"
              :outputType="options.outputType"
              @realTime="realTime"
          />
        </a-col>
        <a-col :span="12" style="height: 300px">
          <div class="preview-box">
            <img v-if="previews.url" :src="previews.url" :style="previews.img"/>
            <span v-else></span>
          </div>
        </a-col>
      </a-row>
      <a-row style="margin-top: 12px">
        <a-col :span="12">
          <a-row>
            <a-col :span="8">
              <a-upload
                  :action="uploadUrl"
                  :headers="headers"
                  :before-upload="beforeUpload"
                  :show-upload-list="false"
              >
                <a-button type="primary" size="small" :icon="h(UploadOutlined)"></a-button>
              </a-upload>
            </a-col>
            <a-col :span="4">
              <a-button :icon="h(PlusCircleOutlined)" size="small" @click="changeScale(1)"></a-button>
            </a-col>
            <a-col :span="4">
              <a-button :icon="h(MinusCircleOutlined)" size="small" @click="changeScale(-1)"></a-button>
            </a-col>
            <a-col :span="4">
              <a-button :icon="h(RotateLeftOutlined)" size="small" @click="rotateLeft()"></a-button>
            </a-col>
            <a-col :span="4">
              <a-button :icon="h(RotateRightOutlined)" size="small" @click="rotateRight()"></a-button>
            </a-col>
          </a-row>
        </a-col>
        <a-col :span="4" :offset="8" style="margin-left: 22.3%">
          <a-button type="primary" @click="avatarUpload()">提 交</a-button>
        </a-col>
      </a-row>
    </a-modal>
  </div>
</template>

<script setup lang="ts">
import {getCurrentInstance, h, reactive, ref, watchEffect} from 'vue';
import {
  MinusCircleOutlined,
  PlusCircleOutlined,
  RotateLeftOutlined,
  RotateRightOutlined,
  UploadOutlined
} from '@ant-design/icons-vue';
import 'vue-cropper/dist/index.css'
import {VueCropper} from 'vue-cropper'
import {useMessage} from "@/hooks/web/useMessage";
import {uploadFile, uploadUrl} from "@/api/common/api";
import {getHeaders} from "@/utils/compUtils";

const cropper = ref();

const headers = getHeaders();
const {createMessage} = useMessage();
const showCropper = ref<boolean>(false)
const {proxy} = getCurrentInstance()
const props = defineProps({
  dialogVisible: {
    type: Boolean,
    default: false
  },
})
watchEffect(() => {
  if (props.dialogVisible) {
    showCropper.value = props.dialogVisible
  } else {
    showCropper.value = false
  }
})

// cropper配置  更多配置可参考 https://www.npmjs.com/package/vue-cropper
const options = reactive({
  img: null, // 裁剪图片的地址
  autoCropWidth: 200, // 默认生成截图框宽度 默认容器的 80%
  autoCropHeight: 200, // 默认生成截图框高度 默认容器的 80%
  outputType: 'png', // 裁剪生成图片的格式 jpeg, png, webp
  autoCrop: true, // 是否默认生成截图框
  fixedBox: false // 固定截图框大小
})
const previews = ref({
  url: ''
})

// 修改图片大小 正数为变大 负数变小
const changeScale = (num) => {
  num = num || 1
  proxy.$refs.cropper.changeScale(num)
}
// 向左边旋转90度
const rotateLeft = () => {
  proxy.$refs.cropper.rotateLeft()
}
// 向右边旋转90度
const rotateRight = () => {
  proxy.$refs.cropper.rotateRight()
}
// 上传图片处理
const beforeUpload = (rawFile) => {
  if (rawFile.type.indexOf('image/') == -1) {
    createMessage.error('请上传图片类型文件!')
    return false
  }
  if (rawFile.size / 1024 / 1024 > 2) {
    createMessage.error('文件大小不能超过2MB!')
    return false
  }
  const reader: any = new FileReader()
  reader.readAsDataURL(rawFile)
  reader.onload = () => {
    options.img = reader.result
  }
}
// 实时预览事件
const realTime = (data) => {
  previews.value = data
}
const emit = defineEmits(['update:dialogVisible', 'confirm']);

// 关闭弹窗
const beforeClose = () => {
  options.img = null
  previews.value.url = ''
  emit('update:dialogVisible', false)
}

// 提交图片
const avatarUpload = () => { // 图片上传事件
  cropper.value.getCropBlob(async (data) => {
    const formData = new FormData();
    formData.append('file', data);  // file是你的文件对
    const result: any = await uploadFile(formData)
    emit('confirm', result.result)
    options.img = null
    previews.value.url = ''
  })
}

</script>

<style lang='scss' scoped>
.avatar-container {
  .img-box {
    border-radius: 50%;
    border: 1px solid #ccc;
    width: 10vw;
    height: 10vw;
  }
}

.preview-box {
  position: absolute;
  top: 50%;
  transform: translate(50%, -50%);
  width: 200px;
  height: 200px;
  border-radius: 50%;
  border: 1px solid #ccc;
  overflow: hidden;
}
</style>
